<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title></title>
<link rel="stylesheet" type="text/css" href="../css/common.css" media="all" />
<link rel="stylesheet" type="text/css" href="../css/article.css" media="all" />
</head>
<body>
<div id="w3h_body">
  <div class="body_content">
    <!-- toc begin -->
    <h1 class="title">RE8010: IE6(Q) IE7(Q) IE8(Q) Chrome(Q) Safari(Q) Opera(Q) Firefox 对多层嵌套的表格级元素百分比高度计算错误</h1>
  <ul class="toc">
      <li><a href="#standard_reference">标准参考</a> <span>•</span></li>
      <li><a href="#description">问题描述</a> <span>•</span></li>
      <li><a href="#influence">造成的影响</a> <span>•</span></li>
      <li><a href="#impacted_browsers">受影响的浏览器</a> <span>•</span></li>
      <li><a href="#analysis_of_issues">问题分析</a> <span>•</span></li>
      <li><a href="#solutions">解决方案</a> <span>•</span></li>
      <li><a href="#see_also">参见</a></li>
    </ul>
    <!-- toc end -->
    <div id="w3h_content">
      <!-- content begin -->
      <address class="author">作者：陆远</address>
      <h2 id="standard_reference">标准参考</h2>
      <p>根据 CSS2.1 规范关于 &quot;百分比&quot; 为单位的 'height' 特性值的计算的描述，当指定一个百分比高度时，百分比的计算基于生成框的包含块的高度。<strong>如果包含块的高度没有明确指定（如依赖于其内容高度），并且这个元素不是绝对定位的，那么高度计算为 auto。</strong></p>
      <p>关于 'height' 特性的更多信息，请参考 CSS2.1 规范 <a href="http://www.w3.org/TR/CSS21/visudet.html#the-height-property">10.5 Content height: the 'height' property</a> 中的内容。</p>

      <h2 id="description">问题描述</h2>
      <p>在表格级元素中，当单元格的高度没有明确指定（如为百分比），其子元素的高度仍然为未明确指定的百分比时，IE 混杂模式及 Firefox 对于这种多层嵌套的表格级元素百分比高度计算将出现错误。</p>

      <h2 id="influence">造成的影响</h2>
      <p>此现象若被触发，可能导致表格元素的高度布局出现很大异常，最终导致页面布局混乱。</p>

      <h2 id="impacted_browsers">受影响的浏览器</h2>
      <table class="list">
        <tr>
          <th>IE6(Q) IE7(Q) IE8(Q) Chrome(S) Safari(S) Opera(Q) Firefox</th>
          <td>&nbsp;</td>
        </tr>
      </table>

      <h2 id="analysis_of_issues">问题分析</h2>
      <p>分析以下代码：</p>
      <pre>&lt;style&gt;
    * { margin:0; padding:0; font:16px/100% Simsun; vertical-align:top; }
&lt;/style&gt;
&lt;body style="height:100px;"&gt;
&lt;div id="<span class="hl_1">cont</span>" style="width:40px; background:#DDD; float:left; margin-right:5px;"&gt;
    &lt;table id="<span class="hl_2">float_cont</span>" cellpadding="0" cellspacing="0" style="width:100%; height:100%; float:left;"&gt;
        &lt;tr&gt;
            &lt;td&gt;
                &lt;table class="<span class="hl_4">sub</span>" cellpadding="0" cellspacing="0" style="width:90%; height:100%; background:#999;"&gt;
                    &lt;tr&gt;
                        &lt;td&gt;AAA&lt;/td&gt;
                    &lt;/tr&gt;
                &lt;/table&gt;
                &lt;table class="<span class="hl_4">sub</span>" cellpadding="0" cellspacing="0" style="width:90%; height:100%; background:#BBB;"&gt;
                    &lt;tr&gt;
                        &lt;td&gt;BBB&lt;/td&gt;
                    &lt;/tr&gt;
                &lt;/table&gt;
            &lt;/td&gt;
        &lt;/tr&gt;
    &lt;/table&gt;
&lt;/div&gt;
&lt;div id="<span class="hl_1">cont</span>" style="width:40px; background:#DDD; float:left; margin-right:5px;"&gt;
    &lt;div id="<span class="hl_2">float_cont</span>" style="display:table; width:100%; height:100%; float:left;"&gt;
        &lt;div class="<span class="hl_4">sub</span>" style="display:table; width:90%; height:100%; background:#999;"&gt;AAA&lt;/div&gt;
        &lt;div class="<span class="hl_4">sub</span>" style="display:table; width:90%; height:100%; background:#BBB;"&gt;BBB&lt;/div&gt;
    &lt;/div&gt;
&lt;/div&gt;
&lt;div id="<span class="hl_1">cont</span>" style="width:40px; background:#DDD; float:left;"&gt;
    &lt;div id="<span class="hl_2">float_cont</span>" style="display:block; width:100%; height:100%; float:left;"&gt;
        &lt;div class="<span class="hl_4">sub</span>" style="display:block; width:90%; height:100%; background:#999;"&gt;AAA&lt;/div&gt;
        &lt;div class="<span class="hl_4">sub</span>" style="display:block; width:90%; height:100%; background:#BBB;"&gt;BBB&lt;/div&gt;
    &lt;/div&gt;
&lt;/div&gt;
&lt;/body&gt;</pre>
      <p>上述代码 BODY 元素高为 100px。其内包含三组元素，每组均为一个宽 40px 的容器 <span class="hl_1">cont</span> 内包含一个宽高均为 100% 的浮动元素 <span class="hl_2">float_cont</span>，这个块级元素内包含了两个高度为 100% 的元素 <span class="hl_4">sub</span>。区别为：</p>
      <ul>
        <li>第一组中容器内包含的为 TABLE 元素嵌套布局；</li>
        <li>第二组中容器内包含的为 display:table，即 TABLE 级别元素的嵌套布局；</li>
        <li>第三组中容器内包含的均为普通的块级元素。</li>
      </ul>
      <p>这段代码在不同浏览器中运行结果如下：</p>
      <table class="compare">
        <tr>
          <th>IE6(Q) IE7(Q) IE8(Q)</th>
          <th>Firefox(Q) Chrome(Q) Safari(Q)</th>
          <th>Firefox(S)</th>
          <th>IE6(S) IE7(S) IE8(S) Chrome(S) Safari(S) Opera(S)</th>
        </tr>
        <tr>
          <td><img src="../../tests/RE8010/table_IE_Q.gif" alt="IE6(Q) IE7(Q) IE8(Q)" /></td>
          <td><img src="../../tests/RE8010/table_FF_Q.gif" alt="Firefox(Q) Chrome(Q) Safari(Q)" /></td>
          <td><img src="../../tests/RE8010/table_FF_S.gif" alt="Firefox(S)" /></td>
          <td><img src="../../tests/RE8010/table_S.gif" alt="IE6(S) IE7(S) IE8(S) Chrome(S) Safari(S) Opera(S)" /></td>
        </tr>
      </table>

      <p>测试代码中 <span class="hl_1">cont</span> 没有明确的设置一个高度，则其 'height' 特性为默认的 auto。而其子元素 <span class="hl_2">float_cont</span> 的 'height' 值为 100%，其内部的 <span class="hl_4">sub</span> 的 'height' 也为 100%。则对于 <span class="hl_2">float_cont</span> 其高度为百分比高度，其具体的计算值取决于其包含块，但是其包含块 <span class="hl_1">cont</span> 的高度又为 auto，根据 CSS2.1 规范，<span class="hl_2">float_cont</span> 的 'height' 特性的值将计算为 auto。此时对于 <span class="hl_4">sub</span> 与其包含块 <span class="hl_2">float_cont</span> 则又出现了上述情况，那么 <span class="hl_4">sub</span> 的 'height' 特性的值也将计算为 auto。</p>
      <p>由此可见：</p>
      <ul>
        <li><em>IE6(S) IE7(S) IE8(S) Chrome(S) Safari(S) Opera</em> 渲染正确。</li>
        <li><em>IE6(Q) IE7(Q) IE8(Q)</em> 中，对普通块级元素与 TABLE 级别元素均渲染错误，而第一组代码出现的现象，则是因为 IE6、IE7 及 IE8(Q) 中 TD 元素无论其 'overflow' 特性为何值，浏览器都将对其溢出的内容进行剪裁。</li>
        <li><em>Firefox(Q) Chrome(Q) Safari(Q)</em> 中，<span class="hl_1">cont</span> 参考了 BODY 元素的 100px 高度作为其计算高度。</li>
        <li><em>Firefox(S)</em> 中，对普通块级元素的渲染正确，但是对 TABLE 级别元素，无论是 TABLE 元素还是 'display' 特性为 table 的元素，均出现了与 IE6(Q) IE7(Q) IE8(Q) 中类似的错误情况。</li>
      </ul>
      <p>IE6(Q) IE7(Q) IE8(Q) 与 Firefox 的错误渲染可以认为：<br />
      浏览器首先将 <span class="hl_2">float_cont</span> 与 <span class="hl_4">sub</span> 的 'height' 特性计算为 auto，最终得到了 <span class="hl_1">cont</span> 的高度为 32px。但此时浏览器再次为 <span class="hl_2">float_cont</span> 与 <span class="hl_4">sub</span> 以设定值 100% 对他们的高度进行了重新计算，导致这三个元素的实际计算高度变为了 32px * 100% = 32px。<br />
      IE6(Q) IE7(Q) IE8(Q) 中则又触发了子元素尺寸超过父容器会撑大父容器尺寸的 Bug。</p>

      <h2 id="solutions">解决方案</h2>
      <p>尽量避免为 TABLE 级别的元素设置百分比为单位的 'height' 特性，以避免 Firefox 对 TABLE 级别元素的高度算法 Bug。</p>

      <h2 id="see_also">参见</h2>
      <h3>知识库</h3>
      <ul class="see_also">
        <li><a href="#">...</a></li>
      </ul>

      <h3>相关问题</h3>
      <ul class="see_also">
        <li><a href="#">...</a></li>
      </ul>

      <div class="appendix">
        <h2>测试环境</h2>
        <table class="list">
          <tr>
            <th>操作系统版本:</th>
            <td>Windows 7 Ultimate build 7600</td>
          </tr>
          <tr>
            <th>浏览器版本:</th>
            <td>
              IE6<br />
              IE7<br />
              IE8<br />
              Firefox 3.6.3<br />
              Chrome 6.0.408.1 dev<br />
              Safari 4.0.5<br />
              Opera 10.53
            </td>
          </tr>
          <tr>
            <th>测试页面:</th>
            <td><a href="../../tests/RE8010/table_height_percent_q.html">table_height_percent_q.html</a><br />
            <a href="../../tests/RE8010/table_height_percent_s.html">table_height_percent_s.html</a>
            </td>
          </tr>
          <tr>
            <th>本文更新时间:</th>
            <td>2010-07-16</td>
          </tr>
        </table>

        <h2>关键字</h2>  
        <!-- keywords begin -->
        <p>TABLE height percent nested 百分比 高度 嵌套 表格</p>
        <!-- keywords end -->
      </div>
      <!-- content end -->
    </div>
  </div>
</div>
</body>
</html>
